package com.zhm.demo.postgresql.config

import com.fasterxml.jackson.databind.ObjectMapper
import org.apache.ibatis.type.BaseTypeHandler
import org.apache.ibatis.type.JdbcType
import org.postgresql.util.PGobject
import java.sql.CallableStatement
import java.sql.PreparedStatement
import java.sql.ResultSet

class PGJsonbTypeHandler : BaseTypeHandler<Map<String, Any>?>() {
    private val objectMapper = ObjectMapper()

    override fun setNonNullParameter(
        ps: PreparedStatement?,
        i: Int,
        parameter: Map<String, Any>?,
        jdbcType: JdbcType?
    ) {
        val jsonbObj = PGobject()
        jsonbObj.type = "jsonb"
        // 将Map转换为JSON字符串
        jsonbObj.value = objectMapper.writeValueAsString(parameter)
        ps?.setObject(i, jsonbObj)
    }

    override fun getNullableResult(rs: ResultSet, columnName: String): Map<String, Any>? {
        val jsonStr = rs.getString(columnName)
        return parseJson(jsonStr)
    }

    override fun getNullableResult(rs: ResultSet, columnIndex: Int): Map<String, Any>? {
        val jsonStr = rs.getString(columnIndex)
        return parseJson(jsonStr)
    }

    override fun getNullableResult(cs: CallableStatement, columnIndex: Int): Map<String, Any>? {
        val jsonStr = cs.getString(columnIndex)
        return parseJson(jsonStr)
    }

    private fun parseJson(jsonStr: String?): Map<String, Any>? {
        if (jsonStr.isNullOrEmpty()) return null
        return objectMapper.readValue(jsonStr, object : com.fasterxml.jackson.core.type.TypeReference<Map<String, Any>>() {})
    }
}